home *** CD-ROM | disk | FTP | other *** search
/ Delphi Magazine Collection 2001 / Delphi Magazine Collection 20001 (2001).iso / DISKS / Issue59 / Arch / Extended Sample / UnitFormBase.pas < prev    next >
Encoding:
Pascal/Delphi Source File  |  2000-06-05  |  5.9 KB  |  229 lines

  1. unit UnitFormBase;
  2. interface
  3.  
  4. uses
  5.   Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
  6.   UnitObjectBase, dbtables, ImgList;
  7.  
  8. type
  9.   TFormBase = class;
  10.   TFormBaseClass = class of TFormBase;
  11.   TFormBase = class(TForm)
  12.     ImageListBase: TImageList;
  13.     procedure FormShow(Sender: TObject);
  14.     procedure FormClose(Sender: TObject; var Action: TCloseAction);
  15.     procedure FormCloseQuery(Sender: TObject; var CanClose: Boolean);
  16.   private
  17.     FKey: integer;
  18.     FBusinessObject: TObjectBase;
  19.     constructor PrivateCreate(Owner: TComponent);
  20.     procedure AncestorInitializeForm;
  21.     procedure AncestorFinalizeForm;
  22.     public function EqualsSignature(aFormClass: TFormBaseClass; const anKey: integer): boolean;
  23.  
  24.   protected
  25.     FStringsFieldForceRole: TStrings;
  26.     class function FindForm(aFormClass: TFormBaseClass; const aKey: integer): TFormBase;
  27.     function GetBusinessObject: TObjectBase;
  28.  
  29.     function BusinessObjectClass: TObjectBaseClass; virtual;
  30.     procedure InitializeForm; virtual;
  31.     procedure FinalizeForm; virtual;
  32.  
  33.   public
  34.  
  35.     constructor Create(Owner: TComponent); override;
  36.  
  37.     class function NewInteger: integer;
  38.  
  39.     class function FormMain: TFormBase;
  40.  
  41.     class function FetchForm(const aKey: integer): TFormBase; virtual;
  42.  
  43.     property Key: integer read FKey write FKey;
  44.  
  45.     property BusinessObject: TObjectBase read GetBusinessObject;
  46.  
  47.     public destructor Destroy; override;
  48.     procedure ShowForm;
  49.     class procedure CloseAll;
  50.     class function FormCount: integer;
  51.     procedure Save;
  52.   end;
  53.  
  54. implementation
  55.  
  56. uses UnitFormMain;
  57.  
  58. {$R *.DFM}
  59.  
  60. var FListForms: TList;
  61.  
  62. procedure TFormBase.ShowForm;
  63. begin
  64.   if (WindowState = wsMinimized) then
  65.     WindowState := wsNormal;
  66.   Show;
  67. end;
  68.  
  69. procedure TFormBase.FormShow(Sender: TObject);
  70. begin
  71.   if (Self = FormMain) then
  72.     Self.SetBounds(0, 0, Self.Width, Self.Height)
  73.   else
  74.       Self.SetBounds(FormMain.Left, (FormMain.Top + FormMain.Height), Self.Width, Self.Height);
  75. end;
  76.  
  77. destructor TFormBase.Destroy;
  78. begin
  79.   FinalizeForm;
  80.   AncestorFinalizeForm;
  81.   FListForms.Remove(Self);
  82.   inherited;
  83. end;
  84.  
  85. function TFormBase.EqualsSignature(
  86.   aFormClass: TFormBaseClass; const anKey: integer): boolean;
  87. begin
  88.   Result := ( (Self.ClassType = aFormClass) and (Self.Key = anKey) );
  89. end;
  90.  
  91. class function TFormBase.FetchForm(const aKey: integer): TFormBase;
  92. begin
  93.   // "Self" in a class method referes to the class type
  94.  
  95.   // See if the form already exists
  96.   Result := FindForm(Self, aKey);
  97.   if (Result = NIL) then begin
  98.     Result := Self.PrivateCreate(Application);
  99.     // Add the newly created form to the list of all existing forms.
  100.     FListForms.Add(Result);
  101.     Result.Key := aKey;
  102.     // Do special ancestor-level initializations.
  103.     Result.AncestorInitializeForm;
  104.     // Now that everything is set up in the architecture run sub-classing
  105.     // form's implementation of InitializeForm
  106.     Result.InitializeForm;
  107.   end; // then begin
  108. end;
  109.  
  110. class function TFormBase.FindForm(aFormClass: TFormBaseClass;
  111.   const aKey: integer): TFormBase;
  112. var i: integer;
  113. var aForm: TFormBase;
  114. begin
  115.   Result := NIL;
  116.   for i := 0 to FListForms.Count - 1 do begin
  117.     aForm := TFormBase(FListForms.Items[i]);
  118.     if ( aForm.EqualsSignature(aFormClass, aKey) ) then begin
  119.       Result := aForm;
  120.       exit;
  121.     end; // then begin
  122.   end; // do begin
  123. end;
  124.  
  125. procedure TFormBase.AncestorInitializeForm;
  126. begin
  127. end;
  128.  
  129. procedure TFormBase.AncestorFinalizeForm;
  130. begin
  131. end;
  132.  
  133. var PrivateClassNewInteger: integer;
  134. class function TFormBase.NewInteger: integer;
  135. begin
  136.   inc(PrivateClassNewInteger);
  137.   Result := PrivateClassNewInteger;
  138. end;
  139.  
  140. function TFormBase.GetBusinessObject: TObjectBase;
  141. begin
  142.   if (FBusinessObject = NIL) and (BusinessObjectClass <> NIL) then
  143.      FBusinessObject := BusinessObjectClass.FetchReference(Self, Key);
  144.   Result := FBusinessObject;
  145. end;
  146.  
  147. procedure TFormBase.FinalizeForm;
  148. begin
  149.   FBusinessObject.FreeReference(Self);
  150.   FBusinessObject := NIL;
  151. end;
  152.  
  153. procedure TFormBase.InitializeForm;
  154. begin
  155. end;
  156.  
  157. function TFormBase.BusinessObjectClass: TObjectBaseClass;
  158. begin
  159.   Result := NIL;
  160. end;
  161.  
  162. class function TFormBase.FormMain: TFormBase;
  163. begin
  164.   Result := UnitFormMain.FormMain; // Be careful not to do a recursive call here.
  165. end;
  166.  
  167. class procedure TFormBase.CloseAll;
  168. var i: integer;
  169. begin
  170.   for i := FListForms.Count - 1 downto 0 do begin
  171.     TFormBase(FListForms.Items[i]).Close;
  172.   end;
  173. end;
  174.  
  175. class function TFormBase.FormCount: integer;
  176. begin
  177.   Result := FListForms.Count;
  178. end;
  179.  
  180. procedure TFormBase.FormClose(Sender: TObject; var Action: TCloseAction);
  181. begin
  182.   Action := caFree;
  183. end;
  184.  
  185. procedure TFormBase.Save;
  186. begin
  187.   if (BusinessObject <> NIL) then
  188.     BusinessObject.Save;
  189. end;
  190.  
  191. procedure TFormBase.FormCloseQuery(Sender: TObject; var CanClose: Boolean);
  192. begin
  193.   CanClose := TRUE;
  194.   // BusinessObject will be NIL for the main form and list forms
  195.   if (BusinessObject <> NIL) and (BusinessObject.UpdatesPending) then begin
  196.     case MessageDlg('Save changes before closing?', mtConfirmation, [mbYes, mbNo, mbCancel], 0) of
  197.       mrYes: BusinessObject.Save;
  198.       mrNo: BusinessObject.Cancel;
  199.       else CanClose := FALSE;
  200.     end; // case
  201.   end; // then begin
  202.  
  203. end;
  204.  
  205. constructor TFormBase.Create(Owner: TComponent);
  206. begin
  207.   inherited;
  208.   // FormMain is the only form that should be auto-created.
  209.   if (Self.ClassType <> TFormMain) then
  210.     MessageDlg('TFormBase.Create is being run. Check that the form ' + Self.Name + ' is not being auto-created.', mtError, [mbOK], 0);
  211. end;
  212.  
  213. constructor TFormBase.PrivateCreate(Owner: TComponent);
  214. begin
  215.   inherited Create(Owner);
  216. end;
  217.  
  218. initialization
  219.  
  220.   FListForms := TList.Create;
  221. {******************************************************************************}
  222.  
  223. finalization
  224.  
  225.   FListForms.Free;
  226. {******************************************************************************}
  227.  
  228. end.
  229.